//package cn.common.config;
//
///**
// * Copyright
// *
// * @Author WuHuang
// * @Date 2022/12/22
// */
//
//import cn.common.annotation.KafkaMetaMessage;
//import cn.common.exceptions.TRetailRuntimeException;
//import com.alibaba.fastjson.JSON;
//import com.google.common.cache.Cache;
//import com.google.common.cache.CacheBuilder;
//import com.tencent.cloud.tsf.lane.service.TsfLaneIdHolder;
//import com.tencent.cloud.tsf.lane.sync.LaneGroup;
//import com.tencent.cloud.tsf.lane.sync.LaneInfo;
//import com.tencent.cloud.tsf.lane.sync.TsfLaneInfoKVLoader;
//import com.tencent.tsf.schedule.consts.TsfMetaVar;
//import lombok.extern.slf4j.Slf4j;
//import org.apache.commons.collections4.CollectionUtils;
//import org.apache.commons.lang.StringUtils;
//import org.apache.skywalking.apm.toolkit.trace.ActiveSpan;
//import org.apache.skywalking.apm.toolkit.trace.TraceContext;
//import org.springframework.tsf.core.consts.HeaderName;
//import org.springframework.tsf.core.context.TsfCoreContext;
//import org.springframework.tsf.core.context.TsfCoreContextHolder;
//import org.springframework.tsf.core.entity.Tag;
//import org.springframework.tsf.core.util.TagUtils;
//import org.springframework.web.context.request.RequestAttributes;
//import org.springframework.web.context.request.RequestContextHolder;
//
//import java.net.InetAddress;
//import java.util.ArrayList;
//import java.util.HashMap;
//import java.util.Iterator;
//import java.util.List;
//import java.util.Map;
//import java.util.Objects;
//import java.util.concurrent.TimeUnit;
//
//import static com.tencent.sr.rmall.springbootstarter.route.TsrRouteConstant.TAG_KEY_SPLIT;
//import static com.tencent.sr.rmall.springbootstarter.route.TsrRouteConstant.TSR_TAG;
//
///**
// * @author effortjiang
// * @date 2020-04-30
// */
//
//@Slf4j
//public class TsfTagUtils {
//
//    private static Cache<String, String> cache = CacheBuilder.newBuilder()
//            .maximumSize(100)
//            .expireAfterWrite(30, TimeUnit.SECONDS)
//            .build();
//
//
//    public static void initKafkaDataRoute(KafkaMetaMessage kafkaMetaMessage) {
//        if (kafkaMetaMessage == null) {
//            throw new TRetailRuntimeException("kafkaMetaMessage is null");
//        }
//        kafkaMetaMessage.setTraceId(TraceContext.traceId());
//        addMsgTags(kafkaMetaMessage);
//    }
//
//
//    public static void initBaseInfo(KafkaMetaMessage kafkaMetaMessage) {
//
//        kafkaMetaMessage.setTimestamp(System.currentTimeMillis());
//        try {
//            InetAddress address = InetAddress.getLocalHost();
//            kafkaMetaMessage.setSenderIp(address.getHostAddress());
//        } catch (Exception e) {
//            log.error("KafkaMetaMessage initBaseInfo error", e);
//        }
//    }
//
//
//    /**
//     * 生产端: 发送消息时, 把请求标记注入KafkaMetaMessage
//     *
//     * @param kafkaMetaMessage
//     */
//    public static void initMsgTags(KafkaMetaMessage kafkaMetaMessage) {
//        try {
//            if (kafkaMetaMessage == null) {
//                log.error("initMsgTags is null");
//                return;
//            }
//            //producer
//            RouteProperties routeProperties = TsrSpringContextAware.getBean(RouteProperties.class);
//            if (routeProperties == null) {
//                log.error("routeProperties is null");
//                return;
//            }
//            if (routeProperties.isOpen()) {
//                addMsgTags(kafkaMetaMessage);
//            } else {
//                log.warn("routeProperties closed");
//            }
//        } catch (Exception e) {
//            log.error("kafka msg initTags error", e);
//        }
//
//    }
//
//    /**
//     * 内部使用,标记为Deprecated, 设置public只是方便单元测试
//     * 业务请使用initMsgTags方法
//     */
//    @Deprecated
//    public static void addMsgTags(KafkaMetaMessage kafkaMetaMessage) {
//        kafkaMetaMessage.putUseTsfTags(new HashMap<>(16));
//
//        TsfCoreContext tsrCoreContext = TsfTagUtils.getDuplicateTsfCoreContext(TsrContextHolder.get());
//        String newDataRouteTag = TsfTagUtils.getDataRouteTag(tsrCoreContext);
//        if (StringUtils.isBlank(newDataRouteTag)) {
//            log.error("initMsgTags newDataRouteTag is null");
//        }
//        List<Tag> tagList = tsrCoreContext.getTags();
//        if (CollectionUtils.isNotEmpty(tagList)) {
//            String encodedTagList = TagUtils.serializeToJson(tagList);
//            kafkaMetaMessage.obtainTsfTags().put(HeaderName.TAG, encodedTagList);
//        }
//
//        List<Tag> systemTags = tsrCoreContext.getSystemTags();
//        if (CollectionUtils.isNotEmpty(systemTags)) {
//            String systemTagList = TagUtils.serializeToJson(systemTags);
//            kafkaMetaMessage.obtainTsfTags().put(HeaderName.SYSTEM_TAG, systemTagList);
//        }
//    }
//
//
//    public static boolean isErrorThread() {
//        //todo 暂时没时间搞 缺提示日志 不影响正常使用
//        return false;
//    }
//
//
//    public static void logRequestId(KafkaMetaMessage kafkaMetaMessage) {
//        try {
//            String traceId = kafkaMetaMessage.getTraceId();
//            String nowTraceId = TraceContext.traceId();
//            if (validReqId(traceId) && validReqId(nowTraceId)) {
//                ActiveSpan.tag("sourceReqId", traceId);
//                log.info("kafkaTraceId_" + traceId + "_link_" + nowTraceId);
//                kafkaMetaMessage.putNeedLogRequestId(false);
//            }
//        } catch (Exception e) {
//            log.error("kafkaMetaMessage logRequestId error!", e);
//        }
//    }
//
//
//    private static boolean validReqId(String traceId) {
//        return StringUtils.isNotBlank(traceId) && !TsrRouteConstant.REQ_ID_NULL.equals(traceId);
//    }
//
//
//    /**
//     * 消费端: 消费消息时, 把请求路由标记从KafkaMetaMessage取出,注入到当前上下文
//     *
//     * @param kafkaMetaMessage
//     */
//    public static void injectContextTag(KafkaMetaMessage kafkaMetaMessage) {
//        try {
//            Map<String, Object> kafkaTags = kafkaMetaMessage.obtainTsfTags();
//            TsfCoreContextHolder.remove();
//            TsrContextHolder.remove();
//
//            if (kafkaTags == null || kafkaTags.size() < 1) {
//                return;
//            }
//            TsfCoreContext tsfCoreContext = TsfCoreContextHolder.get();
//            TsfCoreContext duplicateTsfCoreContext = getDuplicateTsfCoreContext(tsfCoreContext);
//            for (Map.Entry<String, Object> entry : kafkaTags.entrySet()) {
//                String tagString = entry.getValue().toString();
//                if (StringUtils.isNotBlank(tagString)) {
//                    if (HeaderName.TAG.equals(entry.getKey())) {
//                        duplicateTsfCoreContext.setTags(getTagList(tagString));
//                    } else if (HeaderName.SYSTEM_TAG.equals(entry.getKey())) {
//                        duplicateTsfCoreContext.setSystemTags(getTagList(tagString));
//                    }
//                }
//            }
//            TsrContextHolder.set(duplicateTsfCoreContext);
//            TsfCoreContextHolder.set(duplicateTsfCoreContext);
//        } catch (Exception e) {
//            log.error("kafkaMetaMessage injectTag error!", e);
//
//        }
//
//    }
//
//    public static List<Tag> getTagList(String tagString) {
//        List<Tag> resultList = TagUtils.deserializeTagList(tagString);
//        return new ArrayList<>(resultList);
//    }
//
//
//    public static boolean isBackThread() {
//        RequestAttributes attributes = null;
//        try {
//            attributes = RequestContextHolder.getRequestAttributes();
//        } catch (Exception e) {
//            log.error("isWebThread fail", e);
//        }
//        return attributes == null;
//    }
//
//
//    public static boolean isTtlThread() {
//        String name = Thread.currentThread().getName();
//        return StringUtils.isNotBlank(name) && name.contains(TsrExecutorsUtil.TTL_PREFIX);
//    }
//
//
//    /**
//     * 获取跨线程的tsr泳道id
//     *
//     * @return
//     */
//    public static String getTsrLaneId() {
//        TsfCoreContext tsfCoreContext = TsrContextHolder.get();
//        if (tsfCoreContext == null) {
//            log.error("getTsrLaneId tsfCoreContext is null");
//            return null;
//        }
//        List<Tag> systemTags = tsfCoreContext.getSystemTags();
//        String[] laneId = new String[1];
//        systemTags.forEach((systemTag) -> {
//            if (systemTag.getKey().equals("lane")) {
//                laneId[0] = systemTag.getValue();
//            }
//
//        });
//        return laneId[0];
//    }
//
//
//    @Deprecated
//    public static String getLaneId(TsfCoreContext tsfCoreContext) {
//        String[] laneId = new String[1];
//        tsfCoreContext.getSystemTags().forEach((systemTag) -> {
//            if (systemTag.getKey().equals("lane")) {
//                laneId[0] = systemTag.getValue();
//            }
//
//        });
//        return laneId[0];
//    }
//
//
//    public static String getTsrTagKey(String uniqueBusiness, String uniqueId) {
//        return TSR_TAG + TAG_KEY_SPLIT + uniqueBusiness + TAG_KEY_SPLIT + uniqueId;
//    }
//
//
//    /**
//     * 返回当前部署组所在泳道id,如果多个,返回第一个,如果没有返回null
//     */
//    public static String getGroupLaneId() {
//        try {
//            Map<String, LaneInfo> laneInfoMap = TsfLaneInfoKVLoader.getLaneInfoMap();
//            String appId = TsrSpringContextAware.getApplicationContext().getEnvironment().getProperty(TsfMetaVar.GROUP_ID);
//            if (StringUtils.isBlank(appId) || laneInfoMap == null) {
//                return null;
//            }
//            String laneId = cache.getIfPresent(appId);
//            if (StringUtils.isNotBlank(laneId)) {
//                return laneId;
//            }
//            if (laneId != null) {
//                return null;
//            }
//            for (Map.Entry<String, LaneInfo> entry : laneInfoMap.entrySet()) {
//                List<LaneGroup> laneGroupList = entry.getValue().getLaneGroupList();
//                if (CollectionUtils.isNotEmpty(laneGroupList)) {
//                    for (LaneGroup group : laneGroupList) {
//                        if (appId.equals(group.getGroupId())) {
//                            cache.put(appId, entry.getKey());
//                            return entry.getKey();
//                        }
//                    }
//                }
//            }
//            cache.put(appId, "");
//        } catch (Exception e) {
//            log.error("getGroupLaneId error", e);
//        }
//        return null;
//    }
//
//
//    public static void removeLaneContext() {
//        TsfCoreContextHolder.remove();
//        TsrContextHolder.remove();
//    }
//
//
//    /**
//     * 设置泳道id, 数据标
//     */
//    public static void setLaneId(String laneId, String dataRoutTag) {
//        TsfCoreContextHolder.remove();
//        TsrContextHolder.remove();
//        if (StringUtils.isNotBlank(laneId)) {
//            TsfLaneIdHolder.setLaneId(laneId);
//            TsrContextHolder.set(TsfCoreContextHolder.get());
//        }
//        //kafka的数据路由标暂时先传null,改造之后需要把数据标传递过来
//        setDataRouteTag(dataRoutTag);
//    }
//
//    /**
//     * 设置泳道id, 为空则清空
//     */
//    public static void setLaneId(String laneId) {
//        //添加之前只删除掉泳道标，避免把其它标给删除
//        removeLaneId();
//        if (StringUtils.isNotBlank(laneId)) {
//            TsfLaneIdHolder.setLaneId(laneId);
//            TsrContextHolder.set(TsfCoreContextHolder.get());
//        }
//    }
//
//    /**
//     * 删除上下文中的泳道标
//     */
//    public static void removeLaneId() {
//        String laneKey = "lane";
//        removeSystemTag(laneKey);
//    }
//
//    /**
//     * 设置系统数据路由标签
//     *
//     * @param dataRouteTag
//     */
//    public static void setDataRouteTag(String dataRouteTag) {
//        RouteProperties routeProperties = TsrSpringContextAware.getBean(RouteProperties.class);
//        if (routeProperties == null) {
//            return;
//        }
//        if (!routeProperties.isOpen()) {
//            return;
//        }
//        clearAndSaveRouteTag(dataRouteTag);
//    }
//
//    /**
//     * 设置定时任务数据路由标签，业务方禁止使用(定时任务启动时候使用)
//     *
//     * @param dataRouteTag
//     */
//    @Deprecated
//    public static void setCrossSwitchDataRouteTag(String dataRouteTag) {
//        clearAndSaveRouteTag(dataRouteTag);
//    }
//
//
//    /**
//     * 内部使用,标记为Deprecated, 设置public只是方便单元测试
//     * 业务请使用setDataRouteTag方法
//     *
//     * @param dataRouteTag
//     */
//    @Deprecated
//    public static void clearAndSaveRouteTag(String dataRouteTag) {
//        //设置路由标之前先删除数据标签
//        removeDataRouteTag();
//        if (StringUtils.isNotBlank(dataRouteTag)) {
//            TsfCoreContext tsfCoreContext = TsfCoreContextHolder.get();
//            Tag systemTag = new Tag(TsrContextHolder.DATA_RULE_TAG, dataRouteTag, new Tag.ControlFlag[]{Tag.ControlFlag.TRANSITIVE});
//            List<Tag> systemTagList = tsfCoreContext.getSystemTags();
//            systemTagList.add(systemTag);
//            tsfCoreContext.setSystemTags(systemTagList);
//            TsrContextHolder.remove();
//            TsrContextHolder.set(TsfCoreContextHolder.get());
//        }
//    }
//
//
//    /**
//     * 聚合层设置数据标
//     */
//    public static void injectJhDataRouteTag() {
//        RouteProperties routeProperties = TsrSpringContextAware.getBean(RouteProperties.class);
//        if (routeProperties == null) {
//            return;
//        }
//        if (!routeProperties.isOpen()) {
//            return;
//        }
//
//        //优码需要做特殊处理
//        if (routeProperties.isOpen()) {
//            String defaultDataRouteTag = routeProperties.getDefaultDataRouteTag();
//            if (StringUtils.isNotBlank(defaultDataRouteTag)) {
//                TsfTagUtils.setDataRouteTag(defaultDataRouteTag);
//                return;
//            }
//        }
//
//        ProjectProperties projectProperties = TsrSpringContextAware.getBean(ProjectProperties.class);
//        if (projectProperties == null) {
//            return;
//        }
//        if (!projectProperties.getIsOpenDataRoute()) {
//            return;
//        }
//        String serviceType = projectProperties.getServiceType();
//        String dataRouteTag = projectProperties.getDataRouteTag();
//        if (StringUtils.isBlank(serviceType) || StringUtils.isBlank(dataRouteTag)) {
//            log.error("业务定制层未配置数据路由标 projectProperties={}", projectProperties);
//            throw new TMallRuntimeException("业务定制层未配置数据路由标");
//        }
//        //只有业务定制层需要通过切面传递数据标签
//        if ("jh".equals(serviceType)) {
//            setDataRouteTag(dataRouteTag);
//        }
//
//    }
//
//    /**
//     * 删除系统数据路由标签
//     */
//    public static void removeDataRouteTag() {
//        String dataRuleKey = TsrContextHolder.DATA_RULE_TAG;
//        removeSystemTag(dataRuleKey);
//    }
//
//    /**
//     * 删除系统标签
//     *
//     * @param tagName
//     */
//    public static void removeSystemTag(String tagName) {
//        TsfCoreContext tsfCoreContext = TsrContextHolder.get();
//        TsfCoreContext duplicatTsfContext = getDuplicateTsfCoreContext(tsfCoreContext);
//        List<Tag> tagList = duplicatTsfContext.getSystemTags();
//        if (CollectionUtils.isEmpty(tagList)) {
//            TsrContextHolder.remove();
//            TsrContextHolder.set(duplicatTsfContext);
//            TsfCoreContextHolder.remove();
//            TsfCoreContextHolder.set(duplicatTsfContext);
//            return;
//        }
//        Iterator<Tag> iterator = tagList.iterator();
//        while (iterator.hasNext()) {
//            Tag tag = iterator.next();
//            String tagKey = tag.getKey();
//            String dataRuleKey = tagName;
//            if (Objects.equals(tagKey, dataRuleKey)) {
//                iterator.remove();
//            }
//        }
//        TsrContextHolder.remove();
//        TsrContextHolder.set(duplicatTsfContext);
//        TsfCoreContextHolder.remove();
//        TsfCoreContextHolder.set(duplicatTsfContext);
//    }
//
//    /**
//     * 获取数据路由标签,没有则强制报错，避免出现数据错乱
//     *
//     * @return
//     */
//    public static String getDataRouteTag() {
//        TsfCoreContext tsfCoreContext = TsrContextHolder.get();
//        TsfCoreContext duplicateTsfCoreContext = TsfTagUtils.getDuplicateTsfCoreContext(tsfCoreContext);
//        List<Tag> dataRouteTagList = duplicateTsfCoreContext.getSystemTags();
//        log.debug("数据路由标签集合:" + JSON.toJSONString(dataRouteTagList));
//        String ruleValue = getDataRouteTagValue(dataRouteTagList);
//        log.debug("数据路由标签结果:" + ruleValue);
//        return ruleValue;
//    }
//
//
//    private static String getDataRouteTagValue(List<Tag> tagList) {
//        if (org.apache.commons.collections.CollectionUtils.isEmpty(tagList)) {
//            log.error("未获取到数据路由标签");
//            throw new TMallRuntimeException("未获取到数据路由标签");
//        }
//        for (Tag tag : tagList) {
//            String key = tag.getKey();
//            String dataRuleTag = TsrContextHolder.DATA_RULE_TAG;
//            if (Objects.equals(key, dataRuleTag)) {
//                return tag.getValue();
//            }
//        }
//        throw new TMallRuntimeException("未获取到数据路由标签");
//    }
//
//    /**
//     * 获取上下文中的数据路由标签,业务方请使用getDataRouteTag
//     *
//     * @param tsfCoreContext
//     * @return
//     */
//    @Deprecated
//    public static String getDataRouteTag(TsfCoreContext tsfCoreContext) {
//        if (tsfCoreContext == null) {
//            return null;
//        }
//        List<Tag> dataRouteTagList = tsfCoreContext.getSystemTags();
//        if (CollectionUtils.isEmpty(dataRouteTagList)) {
//            return null;
//        }
//        for (Tag tag : dataRouteTagList) {
//            String key = tag.getKey();
//            String dataRuleTag = TsrContextHolder.DATA_RULE_TAG;
//            if (Objects.equals(key, dataRuleTag)) {
//                return tag.getValue();
//            }
//        }
//        return null;
//    }
//
//    public static TsfCoreContext getDuplicateTsfCoreContext(TsfCoreContext transContext) {
//        TsfCoreContext tsfCoreContext = new TsfCoreContext();
//        tsfCoreContext.setTags(getNewTagList(transContext.getTags()));
//        tsfCoreContext.setSystemTags(getNewTagList(transContext.getSystemTags()));
//        tsfCoreContext.setUpstreamTags(getNewTagList(transContext.getUpstreamTags()));
//        tsfCoreContext.setUpstreamSystemTags(getNewTagList(transContext.getUpstreamSystemTags()));
//        return tsfCoreContext;
//    }
//
//    private static List<Tag> getNewTagList(List<Tag> tags) {
//        List<Tag> newTags = new ArrayList<>();
//        if (CollectionUtils.isNotEmpty(tags)) {
//            newTags.addAll(tags);
//        }
//        return newTags;
//    }
//
//    public static String getOptLaneId() {
//        String laneId = getTsrLaneId();
//        if (StringUtils.isEmpty(laneId)) {
//            //再用自己角色泳道
//            laneId = getGroupLaneId();
//        }
//
//        return laneId;
//    }
//    /**
//     * 优先使用线程上下文设置泳道标
//     */
//    public static void setOptLaneId() {
//        String laneId = getOptLaneId();
//        if (!StringUtils.isEmpty(laneId)) {
//            log.info("set current thread laneId: {}", laneId);
//            setLaneId(laneId);
//        }
//    }
//
//}
//
